package com.chen.controller;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.chen.domain.Market;
import com.chen.domain.TurnoverOrder;
import com.chen.dto.MarketDto;
import com.chen.dto.R;
import com.chen.fegin.MarketFegin;
import com.chen.service.MarketService;
import com.chen.service.TurnoverOrderService;
import com.chen.vo.DepthItemVo;
import com.chen.vo.DepthsVo;
import com.chen.vo.TurnoverOrderVo;
import com.google.common.base.Function;
import com.google.common.collect.Lists;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @Author: chen
 * @Date: 2021/5/17 10:20 AM
 * @Version 1.0
 */
@RestController
@Api(tags = "市场相关controller")
@RequestMapping("/markets")
public class MarketController implements MarketFegin {

    @Autowired
    private MarketService marketService;

    @Autowired
    private TurnoverOrderService turnoverOrderService;

    @GetMapping
    @ApiOperation(value = "交易市场的分页查询")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "current", value = "当前页"),
            @ApiImplicitParam(name = "size", value = "每页显示的条数")
    })
    public R<Page<Market>> list(Long tradeAreaId, Integer status, Page<Market> page) {
        Page<Market> list = marketService.page(page, new LambdaQueryWrapper<Market>()
                .eq(tradeAreaId != null, Market::getTradeAreaId, tradeAreaId)
                .eq(status != null, Market::getStatus, status)
                .orderByDesc(Market::getCreated)
        );
        return R.ok(list);
    }

    @GetMapping("/all")
    @ApiOperation(value = "查询所有的交易市场")
    public R<List<Market>> listMarks() {
        return R.ok(marketService.list());
    }

    @PostMapping
    @ApiOperation(value = "新增一个市场")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "market", value = "marketjson")
    })
    public R save(@RequestBody Market market) {
        marketService.saveMarket(market);
        return R.ok();
    }

    @PatchMapping
    @ApiOperation(value = "修改一个市场")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "market", value = "marketjson")
    })
    public R update(@RequestBody Market market) {
        marketService.updateById(market);
        return R.ok();
    }

    @PostMapping("/setStatus")
    @ApiOperation(value = "启用/禁用交易市场")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "market", value = "market的json数据")
    })
    public R status(@RequestBody Market market) {
        marketService.updateById(market);
        return R.ok();
    }

    @ApiOperation(value = "查询成交记录")
    @GetMapping("/trades/{symbol}")
    public R<List<TurnoverOrderVo>> findSymbolTurnoverOrder(@PathVariable("symbol") String symbol) {
        List<TurnoverOrder> turnoverOrders = turnoverOrderService.list(new LambdaQueryWrapper<TurnoverOrder>()
                .eq(TurnoverOrder::getSymbol, symbol)
                .orderByDesc(TurnoverOrder::getCreated)
                .last("limit 20"));
        List<TurnoverOrderVo> turnoverOrderVos = Lists.transform(turnoverOrders, new Function<TurnoverOrder, TurnoverOrderVo>() {
            @NullableDecl
            @Override
            public TurnoverOrderVo apply(@NullableDecl TurnoverOrder turnoverOrder) {
                TurnoverOrderVo turnoverOrderVo = new TurnoverOrderVo();
                Date created = turnoverOrder.getCreated();
                SimpleDateFormat simpleDateFormat = new SimpleDateFormat("HH:mm:ss");

                turnoverOrderVo.setCreated(simpleDateFormat.format(created));

                Market one = marketService.getOne(new LambdaQueryWrapper<Market>()
                        .eq(Market::getSymbol, turnoverOrder.getSymbol()));
                turnoverOrderVo.setCurrentMarket(one);

                turnoverOrderVo.setPrice(turnoverOrder.getDealBuyFee());
                turnoverOrderVo.setVolume(turnoverOrder.getBuyVolume());
                return turnoverOrderVo;
            }
        });
        return R.ok(turnoverOrderVos);
    }

    @GetMapping("/depth/{symbol}/{dep}")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "symbol", value = "交易对"),
            @ApiImplicitParam(name = "dept", value = "深度类型"),
    })
    @ApiOperation(value = "通过的交易对以及深度查询当前的市场的深度数据")
    public R<DepthsVo> depth(@PathVariable("symbol") String symbol, @PathVariable("dep") String dep) {
        DepthsVo depthsVo = new DepthsVo();

        Market market = marketService.getOne(new LambdaQueryWrapper<Market>()
                .eq(Market::getSymbol, symbol));

        //委托买单
        List<DepthItemVo> bids = new ArrayList<>();
        //todo 查询数据
        DepthItemVo bid = new DepthItemVo();
        bid.setPrice(new BigDecimal(100));
        bid.setVolume(new BigDecimal(10));
        bids.add(bid);

        //委托卖单
        List<DepthItemVo> asks = new ArrayList<>();
        DepthItemVo ask = new DepthItemVo();
        ask.setPrice(new BigDecimal(100));
        ask.setVolume(new BigDecimal(10));
        asks.add(ask);

        depthsVo.setAsks(asks);
        depthsVo.setBids(bids);

        depthsVo.setCnyPrice(market.getOpenPrice());
        depthsVo.setPrice(market.getOpenPrice());

        return R.ok(depthsVo);
    }


    @Override
    public MarketDto getMarketBySymbol(String symbol) {
        Market market = marketService.getOne(new LambdaQueryWrapper<Market>()
                .eq(Market::getSymbol, symbol));
        MarketDto marketDto = new MarketDto();
        BeanUtils.copyProperties(market, marketDto);
        return marketDto;
    }

    @Override
    public List<MarketDto> getMarketBySymbols(List<String> symbol) {
        List<Market> market = marketService.list(new LambdaQueryWrapper<Market>()
                .in(Market::getSymbol, symbol));

        return market.stream().map(market1 -> {
            MarketDto marketDto = new MarketDto();
            BeanUtils.copyProperties(market1, marketDto);
            return marketDto;
        }).collect(Collectors.toList());
    }
}
